package com.hua.api.modules.order.service.impl;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.hua.api.core.activemq.ActiveMqConstant;
import com.hua.api.core.activemq.MqMessageBuilder;
import com.hua.api.core.activemq.consumer.event.EventConstant;
import com.hua.api.core.constants.Status;
import com.hua.api.core.framework.util.exception.ApiError;
import com.hua.api.core.properties.SysProperties;
import com.hua.api.core.util.StringUtil;
import com.hua.api.core.util.ValidationUtil;
import com.hua.api.modules.home.service.ActiveMqService;
import com.hua.api.modules.order.dao.OrderInfoDao;
import com.hua.api.modules.order.domain.GoodsInfo;
import com.hua.api.modules.order.domain.OrderInfo;
import com.hua.api.modules.order.domain.OrderItems;
import com.hua.api.modules.order.domain.ShopInfoChannel;
import com.hua.api.modules.order.service.OrderBidService;
import com.hua.api.modules.order.service.OrderInfoService;
import com.hua.api.modules.order.service.dto.OrderInfoCriteria;
import com.hua.api.modules.order.service.dto.SelfOrderDto;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.*;

@Slf4j
@Service
@RequiredArgsConstructor
public class OrderInfoServiceImpl implements OrderInfoService {

    private final OrderInfoDao orderInfoDao;

    private final ActiveMqService activeMqService;

    private final SysProperties sysProperties;

    private final OrderBidService orderBidService;


    // 订单上传审核图
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void onOrderInfoSendImg(String orderNo, String imgPath) {
        log.info("订单上传审核图 onOrderInfoSendImg orderNo:{}, imgPath:{}", orderNo, imgPath);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");

    }

    // 订单完成
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void onOrderInfoFinish(String orderNo) {
        log.info("订单完成 onOrderInfoFinish orderNo:{}", orderNo);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");
        Status.OrderStatus status = Status.OrderStatus.fromValue(orderInfo.getStatus());
        if(status!= Status.OrderStatus.yijiedan){
            log.warn("订单状态非已接单状态，无法完成订单！ status={}, orderNo={}",orderInfo.getStatus());
            throw ApiError.Type.LOGIC_ERROR.toException("订单状态非已接单状态，无法完成订单！");
        }
        orderInfo.setStatus(Status.OrderStatus.wancheng.getValue());
        orderInfo.setUtime(new Date());
        orderInfoDao.updateObject(orderInfo);

        // 如果有转单的，则设置转单订单状态。
        orderBidService.bidFinish(orderInfo.getId());

        String operateDesc = "订单设置为已完成状态！";
        activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderInfo.getValue(),Status.OrderEvent.orderInfo.getName(),operateDesc);

    }

    // 物流派单
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void onOrderInfoSendPaidan(String orderNo,Integer expressId) {
        log.info("订单开始配送 onOrderInfoSendPaidan orderNo:{},expressId:{}", orderNo,expressId);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        if(null!=orderInfo){
            //
            orderInfo.setExpressId(expressId);
            orderInfo.setUtime(new Date());
            orderInfo.setExpressTime(new Date());
            orderInfo.setLogisticsStatus(Status.LogisticsStatus.daijiedan.getValue());
            orderInfoDao.updateObject(orderInfo);

            String operateDesc = "订单开始呼叫物流！";
            activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderSend.getValue(),Status.OrderEvent.orderSend.getName(),operateDesc);
        }else {
            log.warn("onOrderInfoSendPaidan 订单信息不存在 orderNo={}",orderNo);
        }
    }

    // 物流接单
    @Override
    public void onOrderInfoSendJiedan(String orderNo,String shipperName,String shipperPhone) {
        log.info("订单开始配送 onOrderInfoSendJiedan orderNo:{}", orderNo);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        // ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");
        if(null!=orderInfo){
            Status.LogisticsStatus logisticsStatus = Status.LogisticsStatus.fromValue(orderInfo.getLogisticsStatus());
            if(logisticsStatus == Status.LogisticsStatus.daijiedan){
                orderInfo.setUtime(new Date());
                orderInfo.setShipperName(shipperName);
                orderInfo.setShipperPhone(shipperPhone);
                orderInfo.setLogisticsStatus(Status.LogisticsStatus.yijiedan.getValue());
                orderInfoDao.updateObject(orderInfo);

                String operateDesc = "订单配送有配送员接单 配送员:"+shipperName+",电话="+shipperPhone;
                activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderSend.getValue(),Status.OrderEvent.orderSend.getName(),operateDesc);
            }else {
                log.warn("onOrderInfoSendJiedan 订单配送状态费待配送 orderNo={}",orderNo);
            }
            // 配送信息 待完善
        }else {
            log.warn("onOrderInfoSendJiedan 订单信息不存在 orderNo={}",orderNo);
        }
    }

    // 物流配送
    @Override
    public void onOrderInfoSendPeisong(String orderNo) {
        log.info("订单开始配送 onOrderInfoSendPeisong orderNo:{}", orderNo);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        // ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");
        if(null!=orderInfo){
            orderInfo.setUtime(new Date());
            orderInfo.setLogisticsStatus(Status.LogisticsStatus.peisongzhong.getValue());
            orderInfoDao.updateObject(orderInfo);

            String operateDesc = "订单配送开始配送";
            activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderSend.getValue(),Status.OrderEvent.orderSend.getName(),operateDesc);
            // 配送信息 待完善
        }else {
            log.warn("onOrderInfoSendPeisong 订单信息不存在 orderNo={}",orderNo);
        }
    }



    // 花娃接口 订单开始配送
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void onHuawaOrderInfoSendPeisong(String orderNo,String shipperName,String shipperPhone) {
        log.info("订单开始配送 onOrderInfoSendPeisong orderNo:{}", orderNo);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        // ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");
        if(null!=orderInfo){
            orderInfo.setUtime(new Date());
            orderInfo.setLogisticsStatus(Status.LogisticsStatus.peisongzhong.getValue());
            orderInfo.setShipperName(shipperName); // 配送员
            orderInfo.setShipperPhone(shipperPhone); // 配送电话
            orderInfoDao.updateObject(orderInfo);

            String operateDesc = "花娃平台开始配送 配送员:"+shipperName+",电话="+shipperPhone;
            activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderSend.getValue(),Status.OrderEvent.orderSend.getName(),operateDesc);
            // 配送信息 待完善
        }else {
            log.warn("onOrderInfoSendPeisong 订单信息不存在 orderNo={}",orderNo);
        }
    }

    // 订单配送完成
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void onOrderInfoSendSongda(String orderNo) {
        log.info("订单配送完成 onOrderInfoSendFinish orderNo:{}", orderNo);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");
        if(null!=orderInfo){
            orderInfo.setLogisticsStatus(Status.LogisticsStatus.yisongda.getValue());
            orderInfo.setUtime(new Date());
            orderInfoDao.updateObject(orderInfo);

            String operateDesc = "订单配送完成！";
            activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderSend.getValue(),Status.OrderEvent.orderSend.getName(),operateDesc);
        }
        //
    }

    // 取消配送
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void onOrderInfoSendQuxiao(String orderNo) {
        log.info("订单取消配送 onOrderInfoSendCancel orderNo:{}", orderNo);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        // ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");

        if(null!=orderInfo){
            Status.LogisticsStatus orderStatus = Status.LogisticsStatus.fromValue(orderInfo.getLogisticsStatus());
            // 派单中， 待取货， 配送中状态则修改为取消状态
            if(orderStatus == Status.LogisticsStatus.daijiedan || orderStatus==Status.LogisticsStatus.yijiedan || orderStatus == Status.LogisticsStatus.peisongzhong ){
                orderInfo.setUtime(new Date());
                orderInfo.setLogisticsStatus(Status.LogisticsStatus.yiquxiao.getValue());
                orderInfo.setExpressId(null);
                orderInfo.setShipperPhone(null);
                orderInfo.setShipperName(null);
                orderInfoDao.updateObject(orderInfo);

                String operateDesc = "订单配送已取消！！";
                activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderSend.getValue(),Status.OrderEvent.orderSend.getName(),operateDesc);

            }else{
                log.info("订单取消配送 onOrderInfoSendCancel 配送状态无需修改 ，orderStatusName={} ", orderStatus.getName());
            }
        }else{
            log.info("订单信息为空 orderNo={}",orderNo);
        }


    }



    @Transactional(rollbackFor = Exception.class)
    @Override
    public void orderInfoCreate(SelfOrderDto dto){

        ShopInfoChannel shop = orderInfoDao.getObject(ShopInfoChannel.class,sysProperties.shopInfoChannel);
        ValidationUtil.requireNotNull(shop,"录入店铺信息不存在!");
        Long seq = orderInfoDao.queryDaySeqWithSource(dto.getSource());
        Integer daySeq =seq.intValue()+1;
        OrderInfo orderInfo = changeOrderInfo(dto,daySeq,shop);
        orderInfoDao.saveObject(orderInfo);

        // activeMq 通知订单创建
        String operateDesc = "订单创建完成！";
        activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderInfo.getValue(),"订单创建",operateDesc);


    }

    private OrderInfo changeOrderInfo(SelfOrderDto data,Integer daySeq,ShopInfoChannel shop){

        if( null == data.getList() || data.getList().size()==0){
            throw ApiError.Type.LOGIC_ERROR.toException("请选择订单商品信息！");
        }
        OrderInfo o = new OrderInfo();
        o.setSource(data.getSource());
        o.setChannel(Status.CHANNEL_HUA1000);

        // 订单单号
        String orderNo  = "82"+System.currentTimeMillis()+StringUtil.fillZero(String.valueOf(daySeq),3);
        o.setOrderNo(orderNo);
        if(!StringUtil.isEmpty(data.getShowOrderId())){
            // 三方订单号
            o.setShowOrderId(data.getShowOrderId());
        }else{
            o.setShowOrderId(orderNo);
        }
        // 店铺信息
        o.setWmPoiAddress(shop.getAddress());
        o.setWmPoiName(shop.getName());
        o.setWmPoiPhone(shop.getPhone());
        o.setShopCode(shop.getShopCode());
        o.setShopId(shop.getShopId());
        o.setSrcShopId(shop.getShopId());
        // 订单来源
        o.setSource(data.getSource());


        // 收货人信息,送货时间
        o.setProvince(data.getProvince());
        o.setCity(data.getCity());
        o.setArea(data.getArea());
        o.setRecipientAddress(data.getRecipientAddress()); //收货人地址
        o.setRecipientPhone(data.getRecipientPhone()); //收货人联系电话
        o.setBackupRecipientPhone(data.getBackupRecipientPhone()); //备用手机号
        o.setRecipientName(data.getRecipientName()); //收货人
        o.setLongitude(data.getLongitude()); //经度
        o.setLatitude(data.getLatitude()); //纬度
        o.setGeoType(data.getGeoType()); // 地图类型 amap,baidu
        o.setIsTimer(1); // 送货是否定时时间
        o.setDeliveryTime(data.getDeliveryTime()); // 送达时间
        o.setLastDeliveryTime(data.getLastDeliveryTime());
        o.setCardText(data.getCardText()); // 卡片
        o.setCaution(data.getCaution()); // 备注
        // 订花人电话号码
        o.setOrderPhoneNumber(data.getOrderPhoneNumber());

        //
        o.setDaySeq(daySeq+1);
        o.setPrintTime(0);
        o.setPrintCardTime(0);
        o.setCtime(new Date());
        o.setUtime(new Date());
        o.setHasInvoiced(0); // 无需发票

        // 商品信息o
        List<OrderItems> list = getOrderItems(data,o);
        o.setList(list);
        o.setExpressType(getExpressTypes(list));


        // 金额信息
        Double salePrice = data.getTotal();
        if( null == salePrice){
            salePrice = 0d;
        }
        Double originalPrice = 0d; // 原价
        List<OrderItems> alist = o.getList();
        for(OrderItems it:alist){
            //
            originalPrice+=it.getOriginalPrice();
        }
        Double shippingFee = 0d; //运费
        o.setChannelFee(0d); //渠道服务费
        o.setServiceFee(0d); //我方服务费
        o.setShippingFee(shippingFee); // 配送费用
        o.setOriginalPrice(originalPrice); // 原价总金额
        o.setSalePrice(salePrice); // 商品销售价格
        Double total = StringUtil.isEmpty(data.getTotal())?salePrice:data.getTotal();
        o.setTotal(total); // 用户实际支付金额
        o.setRealMoneyYuan(total); // 实际给商家结算费用
        o.setAccountMoneyYuan(0d); //
        o.setCouponMoneyYuan(0d); // 优惠金额
        o.setVoucherMoneyYuan(0d); // 代金券金额
        o.setDistance(0);
        o.setBill(Status.BillMode.bill_no.getValue()); // 不结算

        o.setLogisticsStatus(Status.LogisticsStatus.daipeisong.getValue());
        o.setStatus(Status.OrderStatus.yijiedan.getValue());
        o.setUserId(sysProperties.memberId);

        return o;
    }


    // 商品信息
    public List<OrderItems> getOrderItems(SelfOrderDto criteria,OrderInfo orderInfo){
        List<OrderItems> list = new ArrayList<>();
        criteria.getList().stream().forEach(e->{

            GoodsInfo goods = orderInfoDao.getObject(GoodsInfo.class,e.getGoodsId());
            if(null!=goods){
                OrderItems item = new OrderItems();
                item.setQuantity(e.getQuantity()); // 数量
                item.setFoodName( "【"+goods.getGoodsName()+"】"+goods.getGoodsText()); // 名称
                item.setImgPath(formatImgs(goods.getImgBanner()));
                item.setSkuId(StringUtil.dealNull(goods.getId()));
                item.setGoodsId(goods.getId()); // goodsId
                item.setOriginalPrice(goods.getGoodsPrice()*e.getQuantity()); // 原价
                item.setActualPrice(goods.getSalePrice()*e.getQuantity()); // 现价
                item.setCouponPrice(0d); // 优惠价格
                item.setPrice(goods.getSalePrice()*e.getQuantity()); // 实际支付金额
                item.setOrderNo(orderInfo.getOrderNo());
                item.setOrder(orderInfo);
                item.setStandard(goods.getStandard());
                list.add(item);
            }
        });
        return list;
    }



    public String getExpressTypes(List<OrderItems> list){
        Set<Integer> set = new HashSet<>();
        for(OrderItems i:list){
            set.add(i.getStandard());
        }
        return set.toString();
    }


    private String formatImgs(String json){
        JSONArray array = JSONArray.parseArray(json);
        StringBuffer sbuf = new StringBuffer();
        for(int i=0;i<array.size();i++){
            if(i>0){
                sbuf.append(",");
            }
            sbuf.append(array.get(i));
        }
        return sbuf.toString();
    }


    @Transactional(rollbackFor = Exception.class)
    @Override
    public void cancelOrderInfo(String orderNo, OrderInfoCriteria dto) {
        log.info("后台系统取消订单 OrderInfoServiceImpl.cancelOrderInfo(orderNo={})",orderNo);
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");
        Status.OrderStatus orderStatus = Status.OrderStatus.fromValue(orderInfo.getStatus());
        ValidationUtil.requireNotNull(dto.getRefundMoney(),"退款金额必填，请输入退款金额！");
        if(orderStatus!=Status.OrderStatus.yijiedan){
            throw ApiError.Type.LOGIC_ERROR.toException("订单状态异常，无法取消！");
        }
        if(dto.getRefundMoney()>orderInfo.getTotal()){
            throw ApiError.Type.LOGIC_ERROR.toException("退款金额大于支付金额，请正确输入。");
        }
    }


    @Transactional(rollbackFor = Exception.class)
    @Override
    public void onStoreAcceptOrder(String orderNo, String storeAddress, String storeName, String storeMobile) {
        OrderInfo orderInfo = orderInfoDao.findOrderInfoWithOrderNo(orderNo);
        ValidationUtil.requireNotNull(orderInfo,"订单信息不存在！");
        orderInfo.setWmPoiAddress(storeAddress);
        orderInfo.setWmPoiName(storeName);
        orderInfo.setWmPoiPhone(storeMobile);
        orderInfoDao.updateObject(orderInfo);

        // activeMq 通知订单创建
        String operateDesc = "花娃店铺接单！storeName:"+storeName+",storeMobile:"+storeMobile+",storeAddress:"+storeAddress;
        activeMqService.onOrderInfoLogger(null,null,orderInfo.getId(),Status.OrderEvent.orderSend.getValue(),Status.OrderEvent.orderSend.getName(),operateDesc);


    }


}
